package com.fvff.sanctuary.model;

import com.fvff.sanctuary.model.embeddable.Priority;
import org.apache.commons.lang.builder.EqualsBuilder;
import org.apache.commons.lang.builder.HashCodeBuilder;
import org.apache.commons.lang.builder.ToStringBuilder;
import org.hibernate.annotations.CollectionOfElements;

import javax.persistence.AttributeOverride;
import javax.persistence.AttributeOverrides;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Embedded;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.JoinTable;
import javax.persistence.ManyToOne;
import javax.persistence.OneToMany;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * Activity
 */
@Entity(name = "ACTIVITY")
public final class Activity implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "Activity_ID")
    private Long id;

    @Column(name = "OPEN_SOCIAL_APP_ID")
    private String openSocialAppId;

    @Column(name = "BODY")
    private String body;

    @Column(name = "BODY_MESSAGE_ID")
    private String bodyMessageId;

    @Column(name = "OPEN_SOCIAL_EXTERNAL_ID")
    private String openSocialExternalId;

    @Column(name = "OPEN_SOCIAL_ID")
    private String openSocialId;

    @OneToMany(cascade = CascadeType.REMOVE, fetch = FetchType.LAZY)
    @JoinTable(name = "ACTIVITY_MEDIA_ITEMS",
            joinColumns = @JoinColumn(name = "ACTIVITY_ID"),
            inverseJoinColumns = @JoinColumn(name = "MEDIA_ITEM_ID"))
    private List<MediaItem> mediaItems = new ArrayList<MediaItem>();

    @Column(name = "POSTED_TIME")
    private Date postedTime;

    @Embedded
    @AttributeOverrides({
            @AttributeOverride(name = "value", column = @Column(name = "PRIORITY"))
    })
    private Priority priority;

    @Column(name = "STREAM_TITLE")
    private String streamTitle;

    @ManyToOne(cascade = CascadeType.REMOVE, fetch = FetchType.LAZY)
    @JoinColumn(name = "STREAM_URL_ID")
    private Url streamUrl;

    @Column(name = "TITLE")
    private String title;

    @Column(name = "TITLE_MESSAGE_ID")
    private String titleMessageId;

    @Column(name = "URL")
    private String url;

    @ManyToOne
    @JoinColumn(name = "PERSON_ID")
    private Person personId;

    public Long getId() {
        return id;
    }

    public void setId(final Long id) {
        this.id = id;
    }

    public String getOpenSocialAppId() {
        return openSocialAppId;
    }

    public void setOpenSocialAppId(final String openSocialAppId) {
        this.openSocialAppId = openSocialAppId;
    }

    public String getBody() {
        return body;
    }

    public void setBody(final String body) {
        this.body = body;
    }

    public String getBodyMessageId() {
        return bodyMessageId;
    }

    public void setBodyMessageId(final String bodyMessageId) {
        this.bodyMessageId = bodyMessageId;
    }

    public String getOpenSocialExternalId() {
        return openSocialExternalId;
    }

    public void setOpenSocialExternalId(final String openSocialExternalId) {
        this.openSocialExternalId = openSocialExternalId;
    }

    public String getOpenSocialId() {
        return openSocialId;
    }

    public void setOpenSocialId(final String openSocialId) {
        this.openSocialId = openSocialId;
    }

    public List<MediaItem> getMediaItems() {
        return mediaItems;
    }

    public void setMediaItems(final List<MediaItem> mediaItems) {
        this.mediaItems = mediaItems;
    }

    public Date getPostedTime() {
        return postedTime;
    }

    public void setPostedTime(final Date postedTime) {
        this.postedTime = postedTime;
    }

    public Priority getPriority() {
        return priority;
    }

    public void setPriority(final Priority priority) {
        this.priority = priority;
    }

    public String getStreamTitle() {
        return streamTitle;
    }

    public void setStreamTitle(final String streamTitle) {
        this.streamTitle = streamTitle;
    }

    public Url getStreamUrl() {
        return streamUrl;
    }

    public void setStreamUrl(final Url streamUrl) {
        this.streamUrl = streamUrl;
    }

    public String getTitle() {
        return title;
    }

    public void setTitle(final String title) {
        this.title = title;
    }

    public String getTitleMessageId() {
        return titleMessageId;
    }

    public void setTitleMessageId(final String titleMessageId) {
        this.titleMessageId = titleMessageId;
    }

    public String getUrl() {
        return url;
    }

    public void setUrl(final String url) {
        this.url = url;
    }

    public Person getPersonId() {
        return personId;
    }

    public void setPersonId(final Person personId) {
        this.personId = personId;
    }

    @Override
    public boolean equals(final Object o) {
        return o != null && (o == this || o.getClass() == getClass() && EqualsBuilder.reflectionEquals(this, o));
    }

    @Override
    public int hashCode() {
        return HashCodeBuilder.reflectionHashCode(this);
    }

    @Override
    public String toString() {
        return new ToStringBuilder(this).
                append("id", id).
                append("personId", personId).
                append("openSocialId", openSocialId).
                append("titleMessageId", titleMessageId).
                append("title", title).
                append("bodyMessageId", bodyMessageId).
                append("body", body).
                toString();
    }
}
